#include "eltoolclass.h"
//用于样机的校检//再改一次能不能提交

// 查表法 低字节CRC值表
const unsigned char crc16_modbus_table_lo[] =
    {
        0x00, 0xC0, 0xC1, 0x01, 0xC3, 0x03, 0x02, 0xC2, 0xC6, 0x06, 0x07, 0xC7, 0x05, 0xC5, 0xC4, 0x04,
        0xCC, 0x0C, 0x0D, 0xCD, 0x0F, 0xCF, 0xCE, 0x0E, 0x0A, 0xCA, 0xCB, 0x0B, 0xC9, 0x09, 0x08, 0xC8,
        0xD8, 0x18, 0x19, 0xD9, 0x1B, 0xDB, 0xDA, 0x1A, 0x1E, 0xDE, 0xDF, 0x1F, 0xDD, 0x1D, 0x1C, 0xDC,
        0x14, 0xD4, 0xD5, 0x15, 0xD7, 0x17, 0x16, 0xD6, 0xD2, 0x12, 0x13, 0xD3, 0x11, 0xD1, 0xD0, 0x10,
        0xF0, 0x30, 0x31, 0xF1, 0x33, 0xF3, 0xF2, 0x32, 0x36, 0xF6, 0xF7, 0x37, 0xF5, 0x35, 0x34, 0xF4,
        0x3C, 0xFC, 0xFD, 0x3D, 0xFF, 0x3F, 0x3E, 0xFE, 0xFA, 0x3A, 0x3B, 0xFB, 0x39, 0xF9, 0xF8, 0x38,
        0x28, 0xE8, 0xE9, 0x29, 0xEB, 0x2B, 0x2A, 0xEA, 0xEE, 0x2E, 0x2F, 0xEF, 0x2D, 0xED, 0xEC, 0x2C,
        0xE4, 0x24, 0x25, 0xE5, 0x27, 0xE7, 0xE6, 0x26, 0x22, 0xE2, 0xE3, 0x23, 0xE1, 0x21, 0x20, 0xE0,
        0xA0, 0x60, 0x61, 0xA1, 0x63, 0xA3, 0xA2, 0x62, 0x66, 0xA6, 0xA7, 0x67, 0xA5, 0x65, 0x64, 0xA4,
        0x6C, 0xAC, 0xAD, 0x6D, 0xAF, 0x6F, 0x6E, 0xAE, 0xAA, 0x6A, 0x6B, 0xAB, 0x69, 0xA9, 0xA8, 0x68,
        0x78, 0xB8, 0xB9, 0x79, 0xBB, 0x7B, 0x7A, 0xBA, 0xBE, 0x7E, 0x7F, 0xBF, 0x7D, 0xBD, 0xBC, 0x7C,
        0xB4, 0x74, 0x75, 0xB5, 0x77, 0xB7, 0xB6, 0x76, 0x72, 0xB2, 0xB3, 0x73, 0xB1, 0x71, 0x70, 0xB0,
        0x50, 0x90, 0x91, 0x51, 0x93, 0x53, 0x52, 0x92, 0x96, 0x56, 0x57, 0x97, 0x55, 0x95, 0x94, 0x54,
        0x9C, 0x5C, 0x5D, 0x9D, 0x5F, 0x9F, 0x9E, 0x5E, 0x5A, 0x9A, 0x9B, 0x5B, 0x99, 0x59, 0x58, 0x98,
        0x88, 0x48, 0x49, 0x89, 0x4B, 0x8B, 0x8A, 0x4A, 0x4E, 0x8E, 0x8F, 0x4F, 0x8D, 0x4D, 0x4C, 0x8C,
        0x44, 0x84, 0x85, 0x45, 0x87, 0x47, 0x46, 0x86, 0x82, 0x42, 0x43, 0x83, 0x41, 0x81, 0x80, 0x40};
// 查表法 高字节CRC值表
const unsigned char crc16_modbus_table_hi[] =
    {
        0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41, 0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81, 0x40,
        0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81, 0x40, 0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41,
        0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81, 0x40, 0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41,
        0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41, 0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81, 0x40,
        0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81, 0x40, 0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41,
        0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41, 0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81, 0x40,
        0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41, 0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81, 0x40,
        0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81, 0x40, 0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41,
        0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81, 0x40, 0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41,
        0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41, 0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81, 0x40,
        0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41, 0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81, 0x40,
        0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81, 0x40, 0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41,
        0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41, 0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81, 0x40,
        0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81, 0x40, 0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41,
        0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81, 0x40, 0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41,
        0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41, 0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81, 0x40};
//查表法
unsigned int crc16_modbus(QByteArray data_value,unsigned int data_length)
{
   unsigned int index;
   unsigned char temp0 = 0xff;
   unsigned char temp1 = 0xff;
   unsigned char i=0;
   while (data_length--)
   {
      index = temp0 ^ ((uchar)data_value[i]);//QByteArray是有符号的，需转无符号
      temp0 = temp1 ^ crc16_modbus_table_hi[index];
      temp1 = crc16_modbus_table_lo[index];
      i++;
   }
   return (temp1 << 8) | temp0;
}

//接收16进制的文本,直接生成最终的要发送的命令
QByteArray HEX字符串转发送命令(QString Str)
{
    QByteArray data;
    unsigned int cv;
    //data=将Str中的文本，去除其中不是16进制的符号，剩下的再转成16进制数。
    data=HEX字符串转HEX数组(过滤非HEX字符(Str));
    cv=crc16_modbus(data,data.length());
    data.append(cv%256);
    data.append(cv/256);
    return data;
}


//检查输入字符的是不是16进制，去除其中不是的符号
QString 过滤非HEX字符(QString ss)
{
    QString ff;


    for(int i=0;i<ss.length();i++)
    {
        if((ss[i] >= '0') && (ss[i] <= '9'))
            ff.append(ss[i]);
        else if((ss[i] >= 'A') && (ss[i] <= 'F'))
            ff.append(ss[i]);
        else if((ss[i] >= 'a') && (ss[i] <= 'f'))
        {
            ff.append(ss[i]);
        }

    }
    return ff;
}



//字符串转Hex(QByteArray)类型
QByteArray HEX字符串转HEX数组(QString hexStr)
{
    QByteArray senddata;
    int len = hexStr.length();

    //长度是偶数，直接转，长度是奇数，最后一个字符前面加个'0'
    if(len%2==0)
    {
        for(int i = 0; i < len; i+=2 )
        {   //拼接每一个转换后的数字
            senddata.append(两HEX字符转1字节数(hexStr[i].toLatin1(),hexStr[i+1].toLatin1()));
        }
    }

    else
    {
        for(int i = 0; i < len; i+=2 )
        {   //拼接每一个转换后的数字
            if(i+1>=len)
               senddata.append(两HEX字符转1字节数('0',hexStr[i].toLatin1()));
            else
               senddata.append(两HEX字符转1字节数(hexStr[i].toLatin1(),hexStr[i+1].toLatin1()));
         }
    }
    return senddata;
}

//将2个字符转换为hex，//00-FF -> 0-255
quint8 两HEX字符转1字节数(quint8 a,quint8 b)
{
    quint8 c;
    if((a >= '0') && (a <= '9'))
        c= a - 0x30;
    else if((a >= 'A') && (a <= 'F'))
        c= a - 'A' + 10;//'A' = 65;
    else if((a >= 'a') && (a <= 'f'))
        c= a - 'a' + 10;//'a' = 97;
    else
        c= 0;

    c*=16;//前面字符需要进位

    if((b >= '0') && (b <= '9'))
        c+= b - 0x30;
    else if((b >= 'A') && (b <= 'F'))
        c+= b - 'A' + 10;//'A' = 65;
    else if((b >= 'a') && (b <= 'f'))
        c+= b - 'a' + 10;//'a' = 97;
    else
        c+= 0;

    return c;
}


QString 两HexQStr字符ASCII(QString 两字符)
{

    //toUInt();只能转0~9的字符，abcdef的字符转不了，需用以下格式
    bool ok;
    quint8 a=两字符.mid(0,1).toUInt(&ok,16);
    quint8 b=两字符.mid(1,1).toUInt(&ok,16);
    quint8 c;
    c=a*16+b;


    QByteArray aa;
    aa.append(c);
//    qDebug()<<"在QByteArrr：C"<<c;
//    qDebug()<<"在QByteArray："<<aa;
    QTextCodec *codec = QTextCodec::codecForName("UTF-8");
    QString ASCII=codec->toUnicode(aa);
    //qDebug()<<"ASCII码在"<<ASCII;
    return ASCII;
}




//字节数组换成为00~FF的16进制多字节字符串,转换后主要用于在UI中显示
QString QBtAy转HEX字符串(QByteArray Str,int 是否有空格)
{
    QString readdata;
    QString temp;
    int len = Str.length();
    int h,l;

    for(int i = 0; i < len; i++ )
    {
        h=quint8(Str[i])/16;//QByteArray保存的是有符号数，需转成无符号
        l=quint8(Str[i])%16;
        switch(h){
            case 0:temp='0';break;
            case 1:temp='1';break;
            case 2:temp='2';break;
            case 3:temp='3';break;
            case 4:temp='4';break;
            case 5:temp='5';break;
            case 6:temp='6';break;
            case 7:temp='7';break;
            case 8:temp='8';break;
            case 9:temp='9';break;
            case 10:temp='A';break;
            case 11:temp='B';break;
            case 12:temp='C';break;
            case 13:temp='D';break;
            case 14:temp='E';break;
            case 15:temp='F';break;
        default:temp='g';
        }
        switch(l){
            case 0:temp+='0';break;
            case 1:temp+='1';break;
            case 2:temp+='2';break;
            case 3:temp+='3';break;
            case 4:temp+='4';break;
            case 5:temp+='5';break;
            case 6:temp+='6';break;
            case 7:temp+='7';break;
            case 8:temp+='8';break;
            case 9:temp+='9';break;
            case 10:temp+='A';break;
            case 11:temp+='B';break;
            case 12:temp+='C';break;
            case 13:temp+='D';break;
            case 14:temp+='E';break;
            case 15:temp+='F';break;
        default:temp='g';
        }

        //拼接每一个转换后的字符
        if(是否有空格){ readdata += temp+" ";}//字节间加空格
        else { readdata += temp;}//字节间不加空格
    }
    return readdata;
}


void 重排03D0函数(接收帧03D0 帧03D0,帧03D0重排struct *帧03D0重排)
{
    帧03D0重排->样机地址=帧03D0.样机地址;
    帧03D0重排->功能码03=帧03D0.功能码03;
    帧03D0重排->功能D0=帧03D0.功能D0;

    int i;
    for(i=0;i<4;i++) 帧03D0重排->错误区0[i]=帧03D0.错误区0[i];
    for(i=0;i<4;i++) 帧03D0重排->错误区1[i]=帧03D0.错误区1[i];
    i=0;
    for(int j=0;i<54;i++)//相邻的两个数相互交换
    {

        if(j) {帧03D0重排->错误ASCII[i]=帧03D0.错误ASCII[i-1]; j=0;}
        else  {帧03D0重排->错误ASCII[i]=帧03D0.错误ASCII[i+1]; j=1;}
    }

    //电压220:       5B 60 00 03变00 03 5B 60
    帧03D0重排->电压A =合成int2301序(帧03D0.电压A);
    帧03D0重排->电压B =合成int2301序(帧03D0.电压B);
    帧03D0重排->电压C =合成int2301序(帧03D0.电压C);
    帧03D0重排->未知18=合成int2301序(帧03D0.未知18);

    帧03D0重排->电流A =合成int2301序(帧03D0.电流A);
    帧03D0重排->电流B =合成int2301序(帧03D0.电流B);
    帧03D0重排->电流C =合成int2301序(帧03D0.电流C);
    帧03D0重排->未知22=合成int2301序(帧03D0.未知22);

    帧03D0重排->未知23=合成int2301序(帧03D0.未知23);
    帧03D0重排->未知24=合成int2301序(帧03D0.未知24);
    帧03D0重排->未知25=合成int2301序(帧03D0.未知25);
    帧03D0重排->未知26=合成int2301序(帧03D0.未知26);

    帧03D0重排->未知27=合成int2301序(帧03D0.未知27);
    帧03D0重排->未知28=合成int2301序(帧03D0.未知28);
    帧03D0重排->未知29=合成int2301序(帧03D0.未知29);
    帧03D0重排->未知30=合成int2301序(帧03D0.未知30);

    帧03D0重排->功率A =合成int2301序(帧03D0.功率A);
    帧03D0重排->功率B =合成int2301序(帧03D0.功率B);
    帧03D0重排->功率C =合成int2301序(帧03D0.功率C);
    帧03D0重排->未知34=合成int2301序(帧03D0.未知34);

    帧03D0重排->无功A =合成int2301序(帧03D0.无功A);
    帧03D0重排->无功B =合成int2301序(帧03D0.无功B);
    帧03D0重排->无功C =合成int2301序(帧03D0.无功C);
    帧03D0重排->未知38=合成int2301序(帧03D0.未知38);

    帧03D0重排->功因A =合成int2301序(帧03D0.功因A);
    帧03D0重排->功因B =合成int2301序(帧03D0.功因B );
    帧03D0重排->功因C =合成int2301序(帧03D0.功因C);
    帧03D0重排->未知42=合成int2301序(帧03D0.未知42);

    帧03D0重排->漏电流=合成int2301序(帧03D0.漏电流);
    帧03D0重排->未知44=合成int2301序(帧03D0.未知44);
    帧03D0重排->未知45=合成int2301序(帧03D0.未知45);
    帧03D0重排->未知46=合成int2301序(帧03D0.未知46);
   // int16_t 温度=帧03D0.温度1[0];
    帧03D0重排->温度1=(帧03D0.温度1[0]<<8)+帧03D0.温度1[1];
    帧03D0重排->温度2=(帧03D0.温度2[0]<<8)+帧03D0.温度2[1];
    帧03D0重排->温度3=(帧03D0.温度3[0]<<8)+帧03D0.温度3[1];
    帧03D0重排->温度4=(帧03D0.温度4[0]<<8)+帧03D0.温度4[1];
    帧03D0重排->温度5=(帧03D0.温度5[0]<<8)+帧03D0.温度5[1];
    帧03D0重排->温度6=(帧03D0.温度6[0]<<8)+帧03D0.温度6[1];
    帧03D0重排->温度7=(帧03D0.温度7[0]<<8)+帧03D0.温度7[1];
    帧03D0重排->温度8=(帧03D0.温度8[0]<<8)+帧03D0.温度8[1];

    帧03D0重排->data_crcL=帧03D0.data_crcL;
    帧03D0重排->data_crch=帧03D0.data_crch;

}



